home *** CD-ROM | disk | FTP | other *** search
-
- package sub_arctic.output;
-
- import sub_arctic.lib.manager;
-
- import java.awt.Graphics;
- import java.awt.Font;
- import java.awt.FontMetrics;
- import java.awt.Color;
- import java.awt.Rectangle;
- import java.awt.Polygon;
- import java.awt.Image;
- import java.awt.image.ImageObserver;
- import java.awt.image.ImageFilter;
- import java.awt.image.RGBImageFilter;
- import java.awt.image.ImageProducer;
- import java.awt.image.FilteredImageSource;
-
- /**
- * A drawable object that draws everything in a uniform color
- * (typically a light gray) offset by a small amount. This is used to
- * cast shadows by drawing objects once offset slightly in gray, then
- * again over the top in normal colors. This drawable operates in two
- * modes: expensive (but slow) or cheap (but fast). In cheap mode, images
- * are drawn as unicolor rectangles. In expensive mode, we process images
- * to properly account for transparency.
- *
- * @author Scott Hudson
- */
- public class shadow_drawable extends drawable {
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** Color we paint everything in */
- protected Color the_color = null;
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** Filter to turn images into our one color */
- protected ImageFilter uni_filter;
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** Do we do expensive but realistic drawing of images, or do we just
- * do their bounding rectangle? Default is to be cheap about it.
- */
- protected boolean _expensive_draw = false;
-
- /** Are currently doing expensive but realistic drawing of images, or do
- * are we just drawing their bounding rectangle?
- */
- public boolean expensive_draw() {return _expensive_draw;}
-
- /** Set whether we draw images realistically, but expensively (slow),
- * or just draw their bounding rectangles (fast).
- */
- public void set_expensive_draw(boolean v)
- {
- _expensive_draw = v;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Full constructor.
- *
- * @param Graphics wrappee Graphics object we are a wrapper around.
- * @param int off_x x offset we draw everything at.
- * @param int off_y y offset we draw everything at.
- * @param Color c color we draw everything in.
- * @param boolean do_expensive_draw do we use expensive mode?
- */
- public shadow_drawable(
- Graphics wrappee,
- int off_x,
- int off_y,
- Color c,
- boolean do_expensive_draw)
- {
- /* let super class initialize based on a copy */
- super(wrappee.create());
-
- /* apply a translation to the wrapped Graphics */
- g.translate(off_x, off_y);
-
- /* apply and save the color */
- g.setColor(c);
- the_color = c;
-
- /* construct a filter for our color */
- uni_filter = new unicolor_filter(the_color);
-
- /* remember how to draw */
- _expensive_draw = do_expensive_draw;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Constructor that defaults to fast drawing
- *
- * @param Graphics wrappee Graphics object we are a wrapper around.
- * @param int off_x x offset we draw everything at.
- * @param int off_y y offset we draw everything at.
- * @param Color c color we draw everything in.
- */
- public shadow_drawable(Graphics wrappee, int off_x, int off_y, Color c)
- {
- this(wrappee,off_x,off_y,c,false);
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Full constructor from a drawable
- *
- * @param drawable wrappee drawable object we are a wrapper around.
- * @param int off_x x offset we draw everything at.
- * @param int off_y y offset we draw everything at.
- * @param Color c color we draw everything in.
- * @param boolean do_expensive_draw do we use expensive mode?
- */
- public shadow_drawable(
- drawable wrappee,
- int off_x,
- int off_y,
- Color c,
- boolean do_expensive_draw)
- {
- /* let super class initialize based on a copy of the Graphics object */
- super(wrappee.g.create());
-
- /* apply a translation to the wrapped Graphics */
- g.translate(off_x, off_y);
-
- /* apply and save the color */
- g.setColor(c);
- the_color = c;
-
- /* construct a filter for our color */
- uni_filter = new unicolor_filter(the_color);
-
- /* remember how to draw */
- _expensive_draw = do_expensive_draw;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Constructor from drawable that defaults to fast drawing
- *
- * @param drawable wrappee drawable object we are a wrapper around.
- * @param int off_x x offset we draw everything at.
- * @param int off_y offset we draw everything at.
- * @param Color c color we draw everything in.
- */
- public shadow_drawable(drawable wrappee, int off_x, int off_y, Color c)
- {
- this(wrappee,off_x,off_y,c,false);
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** Default for x drawing offset (10). */
- public static final int default_off_x = 10;
-
- /** Default for y drawing offset (10). */
- public static final int default_off_y = 10;
-
- /** Default color for drawing (Color.gray). */
- public static final Color default_color = Color.gray;
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Constructor with default color.
- *
- * @param Graphics wrappee Graphics object we are a wrapper around.
- * @param int off_x x offset we draw everything at.
- * @param int off_y y offset we draw everything at.
- */
- public shadow_drawable(Graphics wrappee, int off_x, int off_y)
- {
- this(wrappee, off_x, off_y, default_color);
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Constructor with default shadow offset and color
- *
- * @param Graphics wrappee Graphics object we are a wrapper around.
- */
- public shadow_drawable(Graphics wrappee)
- {
- this(wrappee, default_off_x, default_off_y, default_color);
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override copy() to create a new wrapper also.
- * @return drawable the new shadow_drawable object.
- */
- public drawable copy()
- {
- /* create new wrapper, but don't add translation since g already has it */
- return new shadow_drawable(g.create(), 0,0, the_color, expensive_draw());
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override copy() to create a new wrapper also.
- * @param int x x origin for new drawable.
- * @param int y y origin for new drawable.
- * @param int w width of new drawable.
- * @param int h height of new drawable.
- * @return drawable the new shadow_drawable object.
- */
- public drawable copy(int x, int y, int w, int h)
- {
- /* create new wrapper, but don't add translation since g already has it */
- return new shadow_drawable(g.create(x,y,w,h),0,0,the_color,
- expensive_draw());
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override create() to create a new wrapper also.
- * @return Graphics new shadow_drawable object.
- */
- public Graphics create()
- {
- /* create new wrapper, but don't add translation since g already has it */
- return new shadow_drawable(g.create(), 0,0, the_color, expensive_draw());
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override create() to create a new wrapper also.
- * @param int x x origin for new drawable.
- * @param int y y origin for new drawable.
- * @param int w width of new drawable.
- * @param int h height of new drawable.
- * @return Graphics the new shadow_drawable object.
- */
- public Graphics create(int x, int y, int w, int h)
- {
- /* create new wrapper, but don't add translation since g already has it */
- return new shadow_drawable(g.create(x,y,w,h),0,0,the_color,
- expensive_draw());
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override to set all colors to our color.
- * @param Color c color we were supposed to draw in but don't.
- */
- public void setColor(Color c) {g.setColor(the_color);}
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override to turn into a fill with our color.
- *
- * @param int x source x position.
- * @param int y source y position.
- * @param int w width of copied area.
- * @param int h height of copied area.
- * @param int dx destination x position.
- * @param int dy destination y position.
- */
- public void copyArea(int x, int y, int w, int h, int dx, int dy)
- {g.fillRect(dx,dy,w,h);}
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override to turn clear into fill with our color (since clear is an
- * opaque operation).
- *
- * @param int x x position of area to clear.
- * @param int y y position of area to clear.
- * @param int w width of area to clear.
- * @param int h height of area to clear.
- */
- public void clearRect(int x, int y, int w, int h)
- {g.fillRect(x,y,w,h);}
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Process an image to make a shadow version. This is the expensive version
- * of the operation. Basically we turn all colors to our color, but leave
- * the transparency (alpha) value alone. This requires a pixel by pixel
- * mapping, so it can be slow.
- *
- * @param Image from_img the image that we are filtering to produce a shadow
- * version of.
- */
- protected Image make_shadow(Image from_img)
- {
- ImageProducer shadow_prod;
- Image result;
-
- shadow_prod = new FilteredImageSource(from_img.getSource(),uni_filter);
- result = manager.default_toolkit().createImage(shadow_prod);
- manager.wait_for_image(result);
- return result;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override to filter images, turning all non-transparent colors to ours.
- * This will do either the expensive version via make_shadow() or the
- * cheap version that fills a rectangle depending on the setting of
- * expensive_draw.
- *
- * @param Image img the image to be drawn.
- * @param int x x position to place the image at.
- * @param int y y position to place the image at.
- * @param ImageObserver observer observer to notify us of progress drawing
- * the Image
- * @return boolean undocumented AWT return value (here we always return true).
- */
- public boolean drawImage(Image img, int x, int y, ImageObserver observer)
- {
- /* if we are set to do it right, but slow, do so */
- if (expensive_draw())
- return g.drawImage(make_shadow(img),x,y,observer);
-
- /* otherwise, fill area of image */
- g.fillRect(x,y,img.getWidth(manager.an_observer()),
- img.getHeight(manager.an_observer()));
-
- /* There really isn't any documentation on what this return value
- * is supposed to signify, but it appears to indicate that
- * the image in question was fully loaded and drawn without
- * error, so we can safely return true here.
- */
- return true;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override to filter images, turning all non-transparent colors to ours.
- * This will do either the expensive version via make_shadow() or the
- * cheap version that fills a rectangle depending on the setting of
- * expensive_draw.
- *
- * @param Image img the image to be drawn.
- * @param int x x position to place the image at.
- * @param int y y position to place the image at.
- * @param int w width that image will be scaled to.
- * @param int h height that image will be scaled to.
- * @param ImageObserver observer observer to notify us of progress drawing
- * the Image
- * @return boolean undocumented AWT return value (here we always return true).
- */
- public boolean drawImage(Image img, int x, int y, int w, int h,
- ImageObserver obs)
- {
- /* if we are set to do it right, but slow, do so */
- if (expensive_draw())
- return g.drawImage(make_shadow(img),x,y,w,h,obs);
-
- /* otherwise, fill area of image */
- g.fillRect(x,y,w,h);
- return true;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override to filter images, turning all non-transparent colors to ours.
- * This will do either the expensive version via make_shadow() or the
- * cheap version that fills a rectangle depending on the setting of
- * expensive_draw.
- *
- * @param Image img the image to be drawn.
- * @param int x x position to place the image at.
- * @param int y y position to place the image at.
- * @param Color bgcolor background color.
- * @param ImageObserver observer observer to notify us of progress drawing
- * the Image
- * @return boolean undocumented AWT return value (here we always return true).
- */
- public boolean drawImage(Image img, int x, int y, Color bgcolor,
- ImageObserver obs)
- {
- /* if we are set to do it right, but slow, do so */
- if (expensive_draw())
- return g.drawImage(make_shadow(img),x,y,bgcolor,obs);
-
- /* otherwise, fill area of image */
- g.fillRect(x,y,img.getWidth(manager.an_observer()),
- img.getHeight(manager.an_observer()));
- return true;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override to filter images, turning all non-transparent colors to ours.
- * This will do either the expensive version via make_shadow() or the
- * cheap version that fills a rectangle depending on the setting of
- * expensive_draw.
- *
- * @param Image img the image to be drawn.
- * @param int x x position to place the image at.
- * @param int y y position to place the image at.
- * @param int w width that image will be scaled to.
- * @param int h height that image will be scaled to.
- * @param Color bgcolor background color.
- * @param ImageObserver observer observer to notify us of progress drawing
- * the Image
- * @return boolean undocumented AWT return value (here we always return true).
- */
- public boolean drawImage(Image img, int x, int y, int w, int h, Color bgcolor,
- ImageObserver obs)
- {
- /* if we are set to do it right, but slow, do so */
- if (expensive_draw())
- return g.drawImage(make_shadow(img),x,y,w,h,bgcolor,obs);
-
- /* otherwise, fill area of image */
- g.fillRect(x,y,w,h);
- return true;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Override tiled image drawing, turning all non-transparent colors to ours.
- *
- * @param loaded_image pattern the pattern we tile with
- * @param int x x position to place the image at.
- * @param int y y position to place the image at.
- * @param int w width of area to tile.
- * @param int h height of area to tile.
- * @return boolean undocumented AWT return value (here we always return true).
- */
- public boolean tileImage(loaded_image pattern, int x, int y, int w, int h)
- {
- Image img = pattern.image();
- int size_x = pattern.width();
- int size_y = pattern.height();
- int xpt, ypt;
- Graphics clipped_g;
- boolean v = true;
-
- /* if we are set to do it fast, just do a fill */
- if (!expensive_draw())
- {
- g.fillRect(x,y,w,h);
- return true;
- }
-
- /* Build a shadow copy of the pattern */
- Image shadow_pat = make_shadow(pattern.image());
-
- /* Build a copy of our Graphics object that clips to exactly the size
- * we are clipping into
- */
- clipped_g = g.create();
- clipped_g.clipRect(x,y,w,h);
-
- /* loop over image area drawing tiles until we have filled it */
- for (ypt = y; ypt-y < h; ypt += size_y)
- for (xpt = x; xpt-x < w; xpt += size_x)
- v = clipped_g.drawImage(shadow_pat, xpt, ypt, _ignore);
-
- /* return the last return value we got */
- return v;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
- }
-
- /*---------------------------------------------------------------------*/
-
- /**
- * An image filter class to turn all non-transparent colors to one color.
- * This simply replaces the R, G, and B components of a color with our own,
- * leaving the alpha (transparency) value alone.
- *
- * @see sub_arctic.output.shadow_drawable
- * @author Scott Hudson
- */
- class unicolor_filter extends RGBImageFilter {
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /** Encoding for the color we turn everything into */
- public int one_color;
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * Constructor.
- * @param Color c color that we turn everything to.
- */
- public unicolor_filter(Color c)
- {
- /* flag for the superclass */
- canFilterIndexColorModel = true;
-
- /* encode our color in a 32 bit word. we set high order bits for alpha
- * to 00 here so we can easily add it later.
- */
- one_color = c.getRGB() & 0x00ffffff;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
-
- /**
- * The actual filter that processes every pixel. Here we replace the RGB
- * components with our one color, but leave the transparency value alone.
- *
- * @param int x where the pixel is in the image (we ignore this).
- * @param int y where the pixel is in the image (we ignore this).
- * @param int rgb color encoded in an integer (stored; 0xaarrggbb).
- * @return int integer encoding of the filtered result color.
- */
- public int filterRGB(int x, int y, int rgb)
- {
- /* extract the alpha (transparency) value */
- int alpha = rgb & 0xff000000;
-
- /* return our color with their alpha */
- return alpha | one_color;
- }
-
- /* . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . */
- }
- /*=========================== COPYRIGHT NOTICE ===========================
-
- This file is part of the subArctic user interface toolkit.
-
- Copyright (c) 1996 Scott Hudson and Ian Smith
- All rights reserved.
-
- The subArctic system is freely available for most uses under the terms
- and conditions described in
- http://www.cc.gatech.edu/gvu/ui/sub_arctic/sub_arctic/doc/usage.html
- and appearing in full in the lib/interactor.java source file.
-
- The current release and additional information about this software can be
- found starting at: http://www.cc.gatech.edu/gvu/ui/sub_arctic/
-
- ========================================================================*/
-